﻿using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Audio;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.GamerServices;
using Microsoft.Xna.Framework.Graphics;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Media;
using System.IO;
using System.Runtime.InteropServices;


///This will load the visual tile map.
///All it will do is Draw and update based on values passed from the collision map.
namespace MyImaginaryFriends_Redux.Screens.GamePlayScreen_Classes
{
    class TileMap_Background
    {
        static string BasePath = "Content/GameplayScreenContent/TileMapContent/VisualMaps/BackgroundMaps/";
        static string BaseTexturePath = "GameplayScreenContent/TileMapContent/Tiles/BackgroundTiles";

        private VisibleTile[,] Tiles;

        public TileMap_Background()
        {

        }

        public bool LoadContent(ContentManager content, string currentLevel, bool IsGateActive)
        {
            if (currentLevel == "StartingRoom")
            {
                if (LoadTileMap(content, BasePath + "StartingRoom_Background.txt", IsGateActive))
                    return true;
                else return false;
            }

            if (currentLevel == "Hallway")
            {
                if (LoadTileMap(content, BasePath + "RoomHallway_Background.txt", IsGateActive))
                    return true;
                else return false;
            }

            if (currentLevel == "RoomA")
            {
                if (LoadTileMap(content, BasePath + "RoomA_Background.txt", IsGateActive))
                    return true;
                else return false;
            }
            if (currentLevel == "RoomD")
            {
                if (LoadTileMap(content, BasePath + "RoomD_Background.txt", IsGateActive))
                    return true;
                else return false;
            }

            if (currentLevel == "RoomB")
            {
                if (LoadTileMap(content, BasePath + "RoomB_Background.txt", IsGateActive))
                    return true;
                else return false;
            }
            if (currentLevel == "RoomC")
            {
                if (LoadTileMap(content, BasePath + "RoomC_Background.txt", IsGateActive))
                    return true;
                else return false;
            }
            if (currentLevel == "GateRoom")
            {
                if (LoadTileMap(content, BasePath + "GateRoom_Background.txt", IsGateActive))
                    return true;
                else return false;
            }
            if (currentLevel == "FriendRoom")
            {
                if (LoadTileMap(content, BasePath + "FriendRoom_Background.txt", IsGateActive))
                    return true;
                else return false;
            }

            return false;
        }

        private bool LoadTileMap(ContentManager content, string path, bool IsGateActive)
        {
            int width;
            List<string> lines = new List<string>();

            using (StreamReader reader = new StreamReader(TitleContainer.OpenStream(path)))
            {
                string line = reader.ReadLine();
                width = line.Length;

                while (line != null)
                {
                    lines.Add(line);
                    if (line.Length != width)
                    {
                        throw new Exception(String.Format("The length of line {0} is different from all preceeding lines.", lines.Count));
                    }
                    line = reader.ReadLine();
                }
            }

            Tiles = new VisibleTile[width, lines.Count];


            for (int y = 0; y < Tiles.GetLength(1); ++y)//height
            {
                for (int x = 0; x < Tiles.GetLength(0); ++x)//width
                {
                    char tileType = lines[y][x];

                    Tiles[x, y] = LoadTiles(content, tileType, x, y, IsGateActive);
                }
            }


            return true;
        }

        private VisibleTile LoadTiles(ContentManager content, char tiletype, int x, int y, bool IsGateActive)
        {
            switch (tiletype)
            {
                case '.':
                    return LoadTile(content, null);//empty tile

                case '⌞':
                    return LoadTile(content, "/WhiteWalls/LowerLeftWhiteWall");

                case '⌟':
                    return LoadTile(content, "/WhiteWalls/LowerRightWhiteWall");

                case '⌜':
                    return LoadTile(content, "/WhiteWalls/UpperLeftWhiteWall");

                case '⌝':
                    return LoadTile(content, "/WhiteWalls/UpperRightWhiteWall");

                case '⌈':
                    return LoadTile(content, "/WhiteWalls/UpperLeftWhiteWallFrame");

                case'⌉':
                    return LoadTile(content, "/WhiteWalls/UpperRightWhiteWallFrame");

                case '↿':
                    return LoadTile(content, "/WhiteWalls/MiddleLeftWhiteWall");

                case '↾':
                    return LoadTile(content, "/WhiteWalls/MiddleRightWhiteWall");

                case '-':
                    return LoadTile(content, "/WhiteWalls/MiddleWhiteWall");

                case '_':
                    return LoadTile(content, "/WhiteWalls/LowerMiddleWhiteWall");

                case '=':
                    return LoadTile(content, "/WhiteWalls/UpperMiddleWhiteWall");
               
                case 'T':
                    return LoadTile(content, "/WhiteWalls/BehindGateWhiteWall");

                case '1':
                    return LoadTile(content, "Window 1");

                    //<>
                case '2':
                    return LoadTile(content, "Window 2");

                case '3':
                    return LoadTile(content, "Window 3");
                    //<>

                    //<>
                case '4':
                    return LoadTile(content, "Window 4");

                case '5':
                    return LoadTile(content, "Window 5");

                case '6':
                    return LoadTile(content, "Window 6");
                    //<>

                case '₁'://SUBSCRIPT
                    return LoadTile(content, "Chandelier1");

                case '₂':
                    return LoadTile(content, "Chandelier2");

                case '₃':
                    return LoadTile(content, "Chandelier3");

                case '₄':
                    return LoadTile(content, "Chandelier4");
                
                case '₅':
                    return LoadTile(content, "Chandelier5");
                
                case '₆':
                    return LoadTile(content, "Chandelier6");

                case '₇':
                    return LoadTile(content, "Chandelier7");

                case '₈':
                    return LoadTile(content, "Chandelier8");

                case '⇄':
                    return LoadTile(content, "Painting1");

                case '⇆':
                    return LoadTile(content, "Painting2");

                case '⇇':
                    return LoadTile(content, "Painting3");

                case '⇈':
                    return LoadTile(content, "Painting4");

                case '⇊':
                    return LoadTile(content, "Painting5");




                default:
                    throw new NotSupportedException(String.Format("The Character '{0}' at {1}, {2} is not supported.", tiletype, x, y));
            }
        }

        private VisibleTile LoadTile(ContentManager content, string name)
        {
            if (name == null)
            {
                return new VisibleTile(null);
            }
            else return new VisibleTile(content.Load<Texture2D>(BaseTexturePath + name));
        }

        public void Update()
        {
            //NEED TO UPDATE FOR ANIMATED TILES, POTENTIALLY.
        }


        public void Draw(SpriteBatch spriteBatch, Camera camera, TileMap_Colliding collisionMap)
        {
            // spriteBatch.Begin();

            //calculate the visible range of tiles.
            //left draw distance;
            int left = (int)Math.Floor(camera.v2Position.X / VisibleTile.i_TileWidth);
            //right draw distance
            int right = left + spriteBatch.GraphicsDevice.Viewport.Width / VisibleTile.i_TileWidth + 6;
            right = Math.Min(right, collisionMap.Tiles.GetLength(0));

            for (int y = 0; y < Tiles.GetLength(1); ++y)
            {
                for (int x = left; x < right; ++x)
                {
                    //if there is a visible texture
                    Texture2D texture = Tiles[x, y].t2d_Texture;

                    if (texture != null)
                    {
                        //draw it in screen space
                        Vector2 position = new Vector2(x, y + 0.5f) * VisibleTile.v_Size;
                        spriteBatch.Draw(texture, position, null, Color.White, 0.0f, new Vector2(0, 0), 1.0f, SpriteEffects.None, 1.0f);
                    }
                }
            }


            // spriteBatch.End();
        }

    }
}
